﻿using Essensoft.Paylink.Alipay.Domain;
using Essensoft.Paylink.Alipay.Request;
using Essensoft.Paylink.WeChatPay.V2;
using Essensoft.Paylink.WeChatPay.V2.Request;
using Pay.DTO;
using System.Reflection;
using System.Text.Json;

namespace Pay.Services.Imp
{
	/// <summary>
	/// 微信支付V2服务
	/// </summary>
	partial class PayService
	{
		/// <summary>
		/// V2消费者扫二维码支付
		/// </summary>
		private async Task WechatPayV2QRCodeAsync(PayRequestDto payReq, LayuiResultDto<PayResponseDto> result)
		{
			var model = new WeChatPayUnifiedOrderRequest
			{
				OutTradeNo = payReq.OutTradeNo,
				Body = payReq.Description,
				TotalFee = (int)(payReq.Amount * 100),
				Attach = payReq.Attach,
				SpBillCreateIp = payReq.SpBillCreateIp,
				NotifyUrl = payReq.NotifyUrl,
				TradeType = "NATIVE",
				ProfitSharing = payReq.ProfitSharing
			};
			var rep = await _weChatPayV2Client.ExecuteAsync(model, _payConfig.WeChatPayOption);
			if (rep.ReturnCode != WeChatPayCode.Success || rep.ResultCode != WeChatPayCode.Success)
			{
				result.Code = 10000;
				result.Msg = $"{rep.ErrCode}|{rep.ErrCodeDes}|{rep.ReturnMsg}";
			}
			else
				result.Data.Result = rep.CodeUrl;
		}

		/// <summary>
		/// V2商家扫二维码支付
		/// </summary>
		private async Task WechatPayV2PassiveQRCodeAsync(PayRequestDto payReq, LayuiResultDto<PayResponseDto> result)
		{
			var model = new WeChatPayMicroPayRequest
			{
				OutTradeNo = payReq.OutTradeNo,
				Body = payReq.Description,
				TotalFee = (int)(payReq.Amount * 100),
				Attach = payReq.Attach,
				SpBillCreateIp = payReq.SpBillCreateIp,
				AuthCode = payReq.AuthCode,
				ProfitSharing = payReq.ProfitSharing
			};
			var rep = await _weChatPayV2Client.ExecuteAsync(model, _payConfig.WeChatPayOption);
			if (rep.ReturnCode != WeChatPayCode.Success || rep.ResultCode != WeChatPayCode.Success)
			{
				result.Code = 10000;
				result.Msg = $"{rep.ErrCode}|{rep.ErrCodeDes}|{rep.ReturnMsg}";
			}
			else
				result.Data.Result = rep.Body;
		}

		/// <summary>
		/// V2小程序支付
		/// </summary>
		private async Task WechatPayV2MiniprogramAsync(PayRequestDto payReq, LayuiResultDto<PayResponseDto> result)
		{
			var model = new WeChatPayUnifiedOrderRequest
			{
				OutTradeNo = payReq.OutTradeNo,
				Body = payReq.Description,
				TotalFee = (int)(payReq.Amount * 100),
				Attach = payReq.Attach,
				SpBillCreateIp = payReq.SpBillCreateIp,
				NotifyUrl = payReq.NotifyUrl,
				TradeType = "JSAPI",
				OpenId = payReq.OpenId,
				ProfitSharing = payReq.ProfitSharing
			};
			var rep = await _weChatPayV2Client.ExecuteAsync(model, _payConfig.WeChatPayOption);
			if (rep.ReturnCode != WeChatPayCode.Success || rep.ResultCode != WeChatPayCode.Success)
			{
				result.Code = 10000;
				result.Msg = $"{rep.ErrCode}|{rep.ErrCodeDes}|{rep.ReturnMsg}";
			}
			else
			{
				var req = new WeChatPayMiniProgramSdkRequest
				{
					Package = $"prepay_id={rep.PrepayId}"
				};
				var parameter = await _weChatPayV2Client.ExecuteAsync(req, _payConfig.WeChatPayOption);
				// 将参数(parameter)给 小程序前端 让他调起支付API(https://pay.weixin.qq.com/wiki/doc/api/wxa/wxa_api.php?chapter=7_7&index=5)
				result.Data.Result = JsonSerializer.Serialize(parameter);
			}
		}

		/// <summary>
		/// V2公众号支付
		/// </summary>
		private async Task WechatPayV2MPAsync(PayRequestDto payReq, LayuiResultDto<PayResponseDto> result)
		{
			var model = new WeChatPayUnifiedOrderRequest
			{
				OutTradeNo = payReq.OutTradeNo,
				Body = payReq.Description,
				TotalFee = (int)(payReq.Amount * 100),
				Attach = payReq.Attach,
				SpBillCreateIp = payReq.SpBillCreateIp,
				NotifyUrl = payReq.NotifyUrl,
				TradeType = "JSAPI",
				OpenId = payReq.OpenId,
				ProfitSharing = payReq.ProfitSharing
			};
			var rep = await _weChatPayV2Client.ExecuteAsync(model, _payConfig.WeChatPayOption);
			if (rep.ReturnCode != WeChatPayCode.Success || rep.ResultCode != WeChatPayCode.Success)
			{
				result.Code = 10000;
				result.Msg = $"{rep.ErrCode}|{rep.ErrCodeDes}|{rep.ReturnMsg}";
			}
			else
			{
				var req = new WeChatPayMiniProgramSdkRequest
				{
					Package = $"prepay_id={rep.PrepayId}"
				};
				var parameter = await _weChatPayV2Client.ExecuteAsync(req, _payConfig.WeChatPayOption);
				// 将参数(parameter)给 公众号前端 让他在微信内H5调起支付(https://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=7_7&index=6)
				result.Data.Result = JsonSerializer.Serialize(parameter);
			}
		}

		/// <summary>
		/// V2移动端网页支付
		/// </summary>
		private async Task WechatPayV2MobileWebAsync(PayRequestDto payReq, LayuiResultDto<PayResponseDto> result)
		{
			var model = new WeChatPayUnifiedOrderRequest
			{
				OutTradeNo = payReq.OutTradeNo,
				Body = payReq.Description,
				TotalFee = (int)(payReq.Amount * 100),
				Attach = payReq.Attach,
				SpBillCreateIp = payReq.SpBillCreateIp,
				NotifyUrl = payReq.NotifyUrl,
				TradeType = "MWEB"
			};
			// mweb_url为拉起微信支付收银台的中间页面，可通过访问该url来拉起微信客户端，完成支付,mweb_url的有效期为5分钟。
			var rep = await _weChatPayV2Client.ExecuteAsync(model, _payConfig.WeChatPayOption);
			if (rep.ReturnCode != WeChatPayCode.Success || rep.ResultCode != WeChatPayCode.Success)
			{
				result.Code = 10000;
				result.Msg = $"{rep.ErrCode}|{rep.ErrCodeDes}|{rep.ReturnMsg}";
			}
			else
				result.Data.Result = rep.MwebUrl;
		}

		/// <summary>
		/// V2移动应用APP支付
		/// </summary>
		private async Task WechatPayV2AppAsync(PayRequestDto payReq, LayuiResultDto<PayResponseDto> result)
		{
			var model = new WeChatPayUnifiedOrderRequest
			{
				OutTradeNo = payReq.OutTradeNo,
				Body = payReq.Description,
				TotalFee = (int)(payReq.Amount * 100),
				Attach = payReq.Attach,
				SpBillCreateIp = payReq.SpBillCreateIp,
				NotifyUrl = payReq.NotifyUrl,
				TradeType = "APP",
				ProfitSharing = payReq.ProfitSharing
			};
			var rep = await _weChatPayV2Client.ExecuteAsync(model, _payConfig.WeChatPayOption);
			if (rep.ReturnCode != WeChatPayCode.Success || rep.ResultCode != WeChatPayCode.Success)
			{
				result.Code = 10000;
				result.Msg = $"{rep.ErrCode}|{rep.ErrCodeDes}|{rep.ReturnMsg}";
			}
			else
			{
				var req = new WeChatPayAppSdkRequest
				{
					PrepayId = rep.PrepayId
				};
				var parameter = await _weChatPayV2Client.ExecuteAsync(req, _payConfig.WeChatPayOption);
				// 将参数(parameter)给 ios/android端 让他调起微信APP(https://pay.weixin.qq.com/wiki/doc/api/app/app.php?chapter=8_5)
				result.Data.Result = JsonSerializer.Serialize(parameter);
			}
		}

        /// <summary>
        /// V2退款
        /// </summary>
        private async Task WechatPayV2RefundAsync(RefundRequestDto refundReq, LayuiResultDto<RefundResponseDto> result)
        {
            var model = new WeChatPayRefundRequest
            {
                OutRefundNo = refundReq.RefundNo,
                OutTradeNo = refundReq.OutTradeNo,
                TotalFee = (int)(refundReq.Total * 100),
                RefundFee = (int)(refundReq.RefundAmount * 100),
                RefundDesc = refundReq.Reason,
                NotifyUrl = refundReq.NotifyUrl
			};
            var rep = await _weChatPayV2Client.ExecuteAsync(model, _payConfig.WeChatPayOption);
            if (rep.ReturnCode != WeChatPayCode.Success || rep.ResultCode != WeChatPayCode.Success)
            {
                result.Code = 10000;
                result.Msg = $"{rep.ErrCode}|{rep.ErrCodeDes}|{rep.ReturnMsg}";
            }
            else
                result.Data.Result = rep.Body;
        }
    }
}
